package ar.com.age.distribuidora.presentacion.controller;

import java.util.ArrayList;
import java.util.List;

import javax.faces.application.FacesMessage;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.ViewScoped;
import javax.faces.context.FacesContext;

import org.primefaces.context.RequestContext;
import org.primefaces.event.TransferEvent;
import org.primefaces.model.DualListModel;

import ar.com.age.distribuidora.dominio.Marca;
import ar.com.age.distribuidora.dominio.Producto;
import ar.com.age.distribuidora.dominio.Proveedor;
import ar.com.age.distribuidora.dominio.TipoProducto;
import ar.com.age.distribuidora.dominio.UnidadMedida;
import ar.com.age.distribuidora.presentacion.util.Mensajes;
import ar.com.age.distribuidora.presentacion.util.ServiceLocator;
import ar.com.age.distribuidora.presentacion.util.ValidadorTipoUsuario;

@ManagedBean
@ViewScoped
public class ProductoBean {

	private String codigoRegistrar;
	
	private String nombreRegistrar;
	
	private String estadoRegistrar;
	
	private TipoProducto tipoProductoSeleccionado;
	
	private Marca marcaSeleccionada;
	
	private UnidadMedida unidadMedidaSeleccionada;
	
	private List<TipoProducto> tiposProductos;

	private List<Marca> marcas;
	
	private List<UnidadMedida> unidadesMedidas;
	
    private DualListModel<Proveedor> proveedores;
    
    private DualListModel<Proveedor> proveedoresRegistrar;

    private Producto productoSeleccionado;  

    private Producto productoSeleccionadoDetalles;
    
	private String codigoBuscar; 
	
	private String nombreBuscar;  
	
	private String estadoBuscar; 
	
	private String tipoBuscar;  
	
	private String marcaBuscar;
	
	private List<Producto> productos;
	
	private TipoProducto tipoProductoAux;
	
	private String nombreTipo;
	
	private Marca marcaAux;
	
	private String nombreMarca;
	
	private UnidadMedida unidadMedidadAux;
	
	private String nombreUnidadMedida;

	private boolean panelBuscarVisibilidad;
	
	private boolean panelEditarVisibilidad;

	private boolean panelRegistrarVisibilidad;
	
	public ProductoBean() {

		ValidadorTipoUsuario.validarEmpleado();
		
		List<Proveedor> disponibles = ServiceLocator.getProveedorService().buscarTodos();
		List<Proveedor> insertados = new ArrayList<Proveedor>();
				
		this.proveedores = new DualListModel<Proveedor>(disponibles, insertados);
		this.proveedoresRegistrar = new DualListModel<Proveedor>(disponibles, insertados);
		
		this.tiposProductos = ServiceLocator.getDatosProductoService().buscarTodosTipoProducto();
		this.unidadesMedidas = ServiceLocator.getDatosProductoService().buscarTodosUnidadMedida();
		this.marcas = ServiceLocator.getDatosProductoService().buscarTodosMarca();
		
		this.panelEditarVisibilidad = false;
		this.panelRegistrarVisibilidad = true;
		this.panelBuscarVisibilidad = false;
	}
	
	public boolean isPanelEditarVisibilidad() {
		return panelEditarVisibilidad;
	}

	public void setPanelEditarVisibilidad(boolean panelEditarVisibilidad) {
		this.panelEditarVisibilidad = panelEditarVisibilidad;
	}

	public boolean isPanelBuscarVisibilidad() {
		return panelBuscarVisibilidad;
	}

	public void setPanelBuscarVisibilidad(boolean panelBuscarVisibilidad) {
		this.panelBuscarVisibilidad = panelBuscarVisibilidad;
	}

	public boolean isPanelRegistrarVisibilidad() {
		return panelRegistrarVisibilidad;
	}

	public void setPanelRegistrarVisibilidad(boolean panelRegistrarVisibilidad) {
		this.panelRegistrarVisibilidad = panelRegistrarVisibilidad;
	}

	public UnidadMedida getUnidadMedidadAux() {
		return unidadMedidadAux;
	}

	public void setUnidadMedidadAux(UnidadMedida unidadMedidadAux) {
		this.unidadMedidadAux = unidadMedidadAux;
	}

	public String getNombreUnidadMedida() {
		return nombreUnidadMedida;
	}

	public void setNombreUnidadMedida(String nombreUnidadMedida) {
		this.nombreUnidadMedida = nombreUnidadMedida;
	}

	public Marca getMarcaAux() {
		return marcaAux;
	}

	public void setMarcaAux(Marca marcaAux) {
		this.marcaAux = marcaAux;
	}

	public String getNombreMarca() {
		return nombreMarca;
	}

	public void setNombreMarca(String nombreMarca) {
		this.nombreMarca = nombreMarca;
	}

	public TipoProducto getTipoProductoAux() {
		return tipoProductoAux;
	}


	public void setTipoProductoAux(TipoProducto tipoProductoAux) {
		this.tipoProductoAux = tipoProductoAux;
	}


	public String getNombreTipo() {
		return nombreTipo;
	}


	public void setNombreTipo(String nombreTipo) {
		this.nombreTipo = nombreTipo;
	}


	public String getCodigoRegistrar() {
		return codigoRegistrar;
	}

	public void setCodigoRegistrar(String codigoRegistrar) {
		this.codigoRegistrar = codigoRegistrar;
	}

	public String getNombreRegistrar() {
		return nombreRegistrar;
	}

	public void setNombreRegistrar(String nombreRegistrar) {
		this.nombreRegistrar = nombreRegistrar;
	}

	public String getEstadoRegistrar() {
		return estadoRegistrar;
	}

	public void setEstadoRegistrar(String estadoRegistrar) {
		this.estadoRegistrar = estadoRegistrar;
	}

	public TipoProducto getTipoProductoSeleccionado() {
		return tipoProductoSeleccionado;
	}

	public void setTipoProductoSeleccionado(TipoProducto tipoProductoSeleccionado) {
		this.tipoProductoSeleccionado = tipoProductoSeleccionado;
	}

	public Marca getMarcaSeleccionada() {
		return marcaSeleccionada;
	}

	public void setMarcaSeleccionada(Marca marcaSeleccionada) {
		this.marcaSeleccionada = marcaSeleccionada;
	}

	public UnidadMedida getUnidadMedidaSeleccionada() {
		return unidadMedidaSeleccionada;
	}

	public void setUnidadMedidaSeleccionada(UnidadMedida unidadMedidaSeleccionada) {
		this.unidadMedidaSeleccionada = unidadMedidaSeleccionada;
	}

	public List<TipoProducto> getTiposProductos() {
		return tiposProductos;
	}

	public void setTiposProductos(List<TipoProducto> tiposProductos) {
		this.tiposProductos = tiposProductos;
	}

	public List<Marca> getMarcas() {
		return marcas;
	}

	public void setMarcas(List<Marca> marcas) {
		this.marcas = marcas;
	}

	public List<UnidadMedida> getUnidadesMedidas() {
		return unidadesMedidas;
	}

	public void setUnidadesMedidas(List<UnidadMedida> unidadesMedidas) {
		this.unidadesMedidas = unidadesMedidas;
	}

	public DualListModel<Proveedor> getProveedores() {
		return proveedores;
	}

	public void setProveedores(DualListModel<Proveedor> proveedores) {
		this.proveedores = proveedores;
	}

	public Producto getProductoSeleccionado() {
		return productoSeleccionado;
	}

	public void setProductoSeleccionado(Producto productoSeleccionado) {
		this.productoSeleccionado = productoSeleccionado;
	}

	public Producto getProductoSeleccionadoDetalles() {
		return productoSeleccionadoDetalles;
	}

	public void setProductoSeleccionadoDetalles(
			Producto productoSeleccionadoDetalles) {
		this.productoSeleccionadoDetalles = productoSeleccionadoDetalles;
	}

	public String getCodigoBuscar() {
		return codigoBuscar;
	}

	public void setCodigoBuscar(String codigoBuscar) {
		this.codigoBuscar = codigoBuscar;
	}

	public String getNombreBuscar() {
		return nombreBuscar;
	}

	public void setNombreBuscar(String nombreBuscar) {
		this.nombreBuscar = nombreBuscar;
	}

	public String getEstadoBuscar() {
		return estadoBuscar;
	}

	public void setEstadoBuscar(String estadoBuscar) {
		this.estadoBuscar = estadoBuscar;
	}

	public String getTipoBuscar() {
		return tipoBuscar;
	}

	public void setTipoBuscar(String tipoBuscar) {
		this.tipoBuscar = tipoBuscar;
	}

	public String getMarcaBuscar() {
		return marcaBuscar;
	}

	public void setMarcaBuscar(String marcaBuscar) {
		this.marcaBuscar = marcaBuscar;
	}

	public List<Producto> getProductos() {
		return productos;
	}

	public void setProductos(List<Producto> productos) {
		this.productos = productos;
	}
	
	public DualListModel<Proveedor> getProveedoresRegistrar() {
		return proveedoresRegistrar;
	}

	public void setProveedoresRegistrar(
			DualListModel<Proveedor> proveedoresRegistrar) {
		this.proveedoresRegistrar = proveedoresRegistrar;
	}
	
	
	// Metodos del Bean

	public String registrarProducto() {
		
		if (!proveedoresRegistrar.getTarget().isEmpty()) {

			Producto producto = new Producto();
			producto.setCodigo(codigoRegistrar);
			producto.setEstado(estadoRegistrar);
			producto.setMarca(marcaSeleccionada);
			producto.setNombre(nombreRegistrar);
			producto.setTipoProducto(tipoProductoSeleccionado);
			producto.setUnidadMedida(unidadMedidaSeleccionada);
			producto.setProveedores(proveedoresRegistrar.getTarget());

			ServiceLocator.getProductoService().crearOEditar(producto);
			
			FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_INFO, "Advertencia", "La operacion se ha realizado con exito.");  
			RequestContext.getCurrentInstance().showMessageInDialog(message);
			
			this.nombreRegistrar = null;
			this.codigoRegistrar = null;
			this.estadoRegistrar = null;
			List<Proveedor> disponibles = ServiceLocator.getProveedorService().buscarTodos();
			List<Proveedor> insertados = new ArrayList<Proveedor>();
			
			this.proveedoresRegistrar.setSource(disponibles);
			this.proveedoresRegistrar.setTarget(insertados);
					
			return null;
		} else {

			FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_ERROR, "Error", "No ha seleccionado ningun proveedor.");  
	        RequestContext.getCurrentInstance().showMessageInDialog(message);
			return null;
		}
				
	}
	
	public void transferir(TransferEvent event) { 

		StringBuilder builder = new StringBuilder();  
		for(Object item : event.getItems()) {  
			builder.append(((Proveedor) item).getEmpresa()).append("<br />");  
		}  

		FacesMessage msg = new FacesMessage();  
		msg.setSeverity(FacesMessage.SEVERITY_INFO);  
		msg.setSummary("Items Transferido");  
		msg.setDetail(builder.toString());  

		FacesContext.getCurrentInstance().addMessage(null, msg);  
	} 
	
	
	public String actualizarProducto() {
		
		if (!this.proveedores.getTarget().isEmpty()) {
			
			FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_INFO, "Producto", "Producto editado con exito.");  
			RequestContext.getCurrentInstance().showMessageInDialog(message);
	        
			if (this.productoSeleccionado.getTipoProducto() == null) {
	        	this.productoSeleccionado.setTipoProducto(tipoProductoAux);
	        	this.productoSeleccionado.setMarca(marcaAux);
	        	productoSeleccionado.setUnidadMedida(unidadMedidadAux);
			}
			
			this.productoSeleccionado.setProveedores(this.proveedores.getTarget());
	        
			ServiceLocator.getProductoService().crearOEditar(this.productoSeleccionado);
			
			this.productoSeleccionado = null;
			List<Proveedor> disponibles = ServiceLocator.getProveedorService().buscarTodos();
			List<Proveedor> insertados = new ArrayList<Proveedor>();
			this.proveedores = new DualListModel<Proveedor>(disponibles, insertados);
			
			// para reestablecer los valores
			tipoProductoAux = null;
			nombreTipo = null;
			marcaAux=null;
			nombreMarca=null;
			unidadMedidadAux=null;
			nombreUnidadMedida=null;
			// para volver a setear la lista con todas las tipo de producto, marcas
			this.tiposProductos = ServiceLocator.getDatosProductoService().buscarTodosTipoProducto();
			this.marcas = ServiceLocator.getDatosProductoService().buscarTodosMarca();
			this.unidadesMedidas = ServiceLocator.getDatosProductoService().buscarTodosUnidadMedida();
			
			this.panelEditarVisibilidad = false;
			this.panelRegistrarVisibilidad = true;
		 
			return null;
		} else {
			
			this.productos = ServiceLocator.getProductoService().buscar(codigoBuscar,  nombreBuscar,  estadoBuscar, tipoBuscar,  marcaBuscar);

			FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_INFO, "Advertencia", "No ha seleccionado ningun proveedor.");  
	        RequestContext.getCurrentInstance().showMessageInDialog(message); 
			return null;
		}
	}
	
	public String editarProducto() {
		
		if (this.productoSeleccionado != null) {

			this.panelEditarVisibilidad = true;
			this.panelRegistrarVisibilidad = false;
			this.panelBuscarVisibilidad = false;
			
			List<Proveedor> disponibles = ServiceLocator.getProveedorService().buscarTodos();
			List<Proveedor> insertados = ServiceLocator.getProductoService().retornarProductoConProveedores(productoSeleccionado).getProveedores();

			for(Proveedor prov1 : insertados){

				for(int i = 0; i < disponibles.size(); i++){
					if (prov1.getCodigo().equals(disponibles.get(i).getCodigo())) {
						disponibles.remove(i);
					}
				}
			}

			this.proveedores = new DualListModel<Proveedor>(disponibles, insertados);

			this.tipoProductoAux = this.productoSeleccionado.getTipoProducto();
			this.nombreTipo = this.productoSeleccionado.getTipoProducto().getNombre();
			marcaAux = productoSeleccionado.getMarca();
			nombreMarca= productoSeleccionado.getMarca().getNombre();
			unidadMedidadAux= productoSeleccionado.getUnidadMedida();
			nombreUnidadMedida= productoSeleccionado.getUnidadMedida().getNombre();
			//para eliminar la localidad que tenia... asi no aparece dos veces
			for(int i = 0; i < tiposProductos.size(); i++){
				if (tipoProductoAux.getNombre().equals(tiposProductos.get(i).getNombre())) {
					tiposProductos.remove(i);
				}
				if (marcaAux.getNombre().equals(marcas.get(i).getNombre())) {
					marcas.remove(i);
				}
				if (unidadMedidadAux.getNombre().equals(unidadesMedidas.get(i).getNombre())) {
					unidadesMedidas.remove(i);
				}
			}
		
			return null;

		} else {
			
			FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_INFO, "Advertencia", "No ha seleccionado ningun elemento.");  
	        RequestContext.getCurrentInstance().showMessageInDialog(message);
			return null;
		}	

	}
	
	public String eliminarProducto() {
		
		if (this.productoSeleccionado != null) {

			try {
				ServiceLocator.getProductoService().eliminar(this.productoSeleccionado);
			} catch (Exception e) {

				FacesMessage message2 = new FacesMessage(FacesMessage.SEVERITY_ERROR, "Error", Mensajes.ELEMENTO_ASIGNADO);  
				RequestContext.getCurrentInstance().showMessageInDialog(message2);
				return null;
			}

			this.productoSeleccionado = null;
			this.productos = ServiceLocator.getProductoService().buscar(codigoBuscar,  nombreBuscar,  estadoBuscar, tipoBuscar,  marcaBuscar);
			List<Proveedor> disponibles = ServiceLocator.getProveedorService().buscarTodos();
			List<Proveedor> insertados = new ArrayList<Proveedor>();
			
			this.proveedores.setSource(disponibles);
			this.proveedores.setTarget(insertados);

			FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_INFO, "Advertencia", Mensajes.OPERACION_EXITOSA);  
			RequestContext.getCurrentInstance().showMessageInDialog(message);
			
			return null;

		} else {
			
			FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_INFO, "Advertencia", Mensajes.ELEMENTO_NO_SELECCIONADO);  
	        RequestContext.getCurrentInstance().showMessageInDialog(message);
			return null;
		}	

	}
	
	public String buscarProducto() {
		
		this.productos = ServiceLocator.getProductoService().buscar(codigoBuscar,  nombreBuscar,  estadoBuscar, tipoBuscar,  marcaBuscar);

		if (this.productos != null && !this.productos.isEmpty()) {

			return null;

		} else {
			
			FacesMessage message = new FacesMessage(FacesMessage.SEVERITY_INFO, "Advertencia", "No se encotraron resultados para la busqueda.");  
			RequestContext.getCurrentInstance().showMessageInDialog(message);
			return null;
		}
	}

	public void visibilizarBuscar() {
		
		panelBuscarVisibilidad = true;
		panelEditarVisibilidad = false;
		panelRegistrarVisibilidad = false;
	}
	
	public void visibilizarRegistrar() {
		
		panelBuscarVisibilidad = false;
		panelEditarVisibilidad = false;
		panelRegistrarVisibilidad = true;
	}
	
	public void volverBusqueda() {
		
		panelBuscarVisibilidad = true;
		panelEditarVisibilidad = false;
		this.productos = ServiceLocator.getProductoService().buscar(codigoBuscar,  nombreBuscar,  estadoBuscar, tipoBuscar,  marcaBuscar);
	}
}
